// Package main 演示GORM高级查询操作，包括分页查询和Scope可重用查询逻辑功能
// 本示例展示了如何在GORM中实现分页查询以及如何创建和使用可重用的查询逻辑
package main

import (
	"fmt"
	"gin-gorm/global"
	"gin-gorm/models"

	"gorm.io/gorm"
)

// HighQuery 演示分页和Scope功能
// 该函数包含了GORM中的分页查询和Scope功能的使用示例
func HighQuery() {

	// var userList []models.UserModel
	// limit := 2  // 每页记录数
	// page := 1   // 当前页码

	// 简单分页示例 - 第一页数据
	// 分页查询通过Limit和Offset方法实现，Limit指定每页记录数，Offset指定偏移量
	// global.DB.Limit(2).Offset(0).Find(&userList)  // 获取前2条记录（第一页）
	// fmt.Println(userList)

	// 简单分页示例 - 第二页数据
	// 偏移量为2，表示跳过前2条记录，从第3条开始获取
	// global.DB.Limit(2).Offset(2).Find(&userList)  // 获取第3-4条记录（第二页）
	// fmt.Println(userList)

	// 分页公式
	// 标准分页公式：偏移量 = (当前页码 - 1) * 每页记录数
	// 这种方式可以根据页码动态计算偏移量，适用于前端分页请求
	// global.DB.Limit(limit).Offset((page - 1) * limit).Find(&userList)
	// fmt.Println(userList)

	// Scope功能
	// Scope是GORM中可重用的查询逻辑，可以将常用的查询条件封装成函数，提高代码复用性
	// Scope允许将复杂的查询条件抽象为可重用的函数，使代码更加清晰和易于维护
	var userList []models.UserModel
	// 使用自定义的Age18 Scope进行查询
	// 无参数Scope直接传递函数名
	// global.DB.Scopes(Age18).Find(&userList) // 查询年龄大于18的用户
	// 使用带参数的NameIn Scope进行查询
	// 带参数Scope需要先调用函数获取闭包，再传递给Scopes方法
	global.DB.Scopes(NameIn("枫枫", "张三")).Find(&userList) // 查询名字在指定列表中的用户
	fmt.Println(userList)

}

// Age18 无参数自定义Scope函数，用于查询年龄大于18的记录
// Scope函数必须接收*gorm.DB类型的参数，并返回*gorm.DB类型的结果
// 无参数Scope的定义形式简单，直接实现查询逻辑并返回修改后的DB对象
func Age18(tx *gorm.DB) *gorm.DB {
	return tx.Where("age > 18") // 添加查询条件：年龄大于18
}

// NameIn 带参数的自定义Scope函数，用于查询名字在指定列表中的记录
// 带参数Scope返回一个闭包函数，该闭包接收*gorm.DB参数并返回*gorm.DB结果
// 这种方式允许在创建Scope时传入参数，使查询逻辑更加灵活
func NameIn(nameList ...string) func(tx *gorm.DB) *gorm.DB {
	// 返回一个闭包函数，该函数捕获了外部的nameList参数
	return func(tx *gorm.DB) *gorm.DB {
		return tx.Where("name in ?", nameList) // 添加查询条件：名字在指定列表中
	}
}

// main 程序入口函数
func main() {
	// 初始化数据库连接
	global.Connect()
	HighQuery()

}
